From 7047502d846713fee8f271354c86afa5dd63ffdd Mon Sep 17 00:00:00 2001 From: Tristan Van Berkom Date: Mon, 27 Sep 2010 21:15:16 +0900 Subject: [PATCH] Fix erroneous usage of height-for-width apis in gtk_widget_real_adjust_size_allocation(). When fitting a widget into its allocation, the second dimension is always dependent on the first, so gtk_widget_get_preferred_size() cannot be used directly (because we want the natural height for the allocated width, not the natural height for the natural width, which is generally a smaller height than the height-for-minimum-width or height-for-allocated-width). Added test to testadjustsize to ensure proper behaviour. --- gtk/gtkwidget.c | 47 ++++++++++++++++++++++++++++++------------ tests/testadjustsize.c | 35 +++++++++++++++++++++++++++++++ 2 files changed, 69 insertions(+), 13 deletions(-) diff --git a/gtk/gtkwidget.c b/gtk/gtkwidget.c index 9472578cc1..b4499e7515 100644 --- a/gtk/gtkwidget.c +++ b/gtk/gtkwidget.c @@ -4685,23 +4685,44 @@ gtk_widget_real_adjust_size_allocation (GtkWidget *widget, GtkAllocation *allocation) { const GtkWidgetAuxInfo *aux_info; - GtkRequisition min, natural; + gint natural_width; + gint natural_height; int x, y, w, h; aux_info = _gtk_widget_get_aux_info_or_defaults (widget); - gtk_widget_get_preferred_size (widget, &min, &natural); - - get_span_inside_border_horizontal (widget, - aux_info, - allocation->width, - natural.width, - &x, &w); - get_span_inside_border_vertical (widget, - aux_info, - allocation->height, - natural.height, - &y, &h); + if (gtk_widget_get_request_mode (widget) == GTK_SIZE_REQUEST_HEIGHT_FOR_WIDTH) + { + gtk_widget_get_preferred_width (widget, NULL, &natural_width); + get_span_inside_border_horizontal (widget, + aux_info, + allocation->width, + natural_width, + &x, &w); + + gtk_widget_get_preferred_height_for_width (widget, w, NULL, &natural_height); + get_span_inside_border_vertical (widget, + aux_info, + allocation->height, + natural_height, + &y, &h); + } + else /* GTK_SIZE_REQUEST_WIDTH_FOR_HEIGHT */ + { + gtk_widget_get_preferred_height (widget, NULL, &natural_height); + get_span_inside_border_vertical (widget, + aux_info, + allocation->height, + natural_height, + &y, &h); + + gtk_widget_get_preferred_width_for_height (widget, h, NULL, &natural_width); + get_span_inside_border_horizontal (widget, + aux_info, + allocation->width, + natural_width, + &x, &w); + } allocation->x += x; allocation->y += y; diff --git a/tests/testadjustsize.c b/tests/testadjustsize.c index 5e9795c824..889ea52c72 100644 --- a/tests/testadjustsize.c +++ b/tests/testadjustsize.c @@ -394,6 +394,40 @@ open_margin_window (void) gtk_widget_show_all (test_window); } +static void +open_valigned_label_window (void) +{ + GtkWidget *window, *box, *label, *frame; + + window = gtk_window_new (GTK_WINDOW_TOPLEVEL); + + g_signal_connect (test_window, "delete-event", + G_CALLBACK (gtk_main_quit), test_window); + + box = gtk_vbox_new (FALSE, 0); + gtk_widget_show (box); + gtk_container_add (GTK_CONTAINER (window), box); + + + label = gtk_label_new ("Some wrapping text with width-chars = 15 and max-width-chars = 35"); + gtk_label_set_line_wrap (GTK_LABEL (label), TRUE); + gtk_label_set_width_chars (GTK_LABEL (label), 15); + gtk_label_set_max_width_chars (GTK_LABEL (label), 35); + + gtk_widget_show (label); + + frame = gtk_frame_new (NULL); + gtk_widget_show (frame); + gtk_container_add (GTK_CONTAINER (frame), label); + + gtk_widget_set_valign (frame, GTK_ALIGN_CENTER); + gtk_widget_set_halign (frame, GTK_ALIGN_FILL); + + gtk_box_pack_start (GTK_BOX (box), frame, TRUE, TRUE, 0); + + gtk_window_present (GTK_WINDOW (window)); +} + int main (int argc, char *argv[]) { @@ -403,6 +437,7 @@ main (int argc, char *argv[]) open_control_window (); open_alignment_window (); open_margin_window (); + open_valigned_label_window (); gtk_main (); -- 2.30.2